package com.ctbri.JWLetter.service.impl;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;

import javax.annotation.Resource;

import org.springframework.stereotype.Service;

import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.util.TypeUtils;
import com.ctbri.JWLetter.bean.Letter;
import com.ctbri.JWLetter.bean.Link;
import com.ctbri.JWLetter.dao.es.LetterDao;
import com.ctbri.JWLetter.dao.neo4j.NodeDao;
import com.ctbri.JWLetter.frame.Consts;
import com.ctbri.JWLetter.frame.JWJSONObject;
import com.ctbri.JWLetter.service.RelationGraphService;
import com.ctbri.JWLetter.type.error.ErrorCode;
import com.ctbri.JWLetter.util.page.PageResult;

/**
 * 知识图谱业务层实现
 * 
 * @author Hogan
 *
 */
@Service("graphService")
public class RelationGraphServiceImpl implements RelationGraphService {

	@Resource
	private NodeDao nodeDao;

	@Resource
	private LetterDao letterDao;

	@SuppressWarnings("unchecked")
	@Override
	public JWJSONObject loadGraph(JSONObject jParams) {
		JWJSONObject result = new JWJSONObject();
		JSONObject detail = new JSONObject();
		String word = jParams.getString("word");
		Map<String, Object> nodesAndLinks = nodeDao.findNodesByWord(word);
		detail.put("nodes", nodesAndLinks.get("nodes"));
		detail.put("links", nodesAndLinks.get("links"));
		detail.put("letterIds", generateLetterIds((List<Link>) nodesAndLinks.get("links")));
		result.setDetail(detail);
		result.setErrorCode(ErrorCode.SUCCESS);
		return result;
	}

	@Override
	public JWJSONObject loadRelationLetters(JSONObject jParams) {
		JWJSONObject result = new JWJSONObject();
		JSONObject detail = new JSONObject();
		List<Integer> modifiedLetterIds = new ArrayList<Integer>();
		Integer[] letterIds = castToIntegers(jParams.getString("letterIds"));
		Integer pageNum = jParams.getInteger("pageNum");
		PageResult<Letter> pageResult = new PageResult<Letter>();
		pageResult.setPerPage(Consts.PAGE_SIZE_RELATION_LETTER);
		pageResult.setCurrentPage(pageNum);
		int startCount = (pageResult.getCurrentPage() - 1) * Consts.PAGE_SIZE_RELATION_LETTER;
		if (startCount < letterIds.length) {
			for (int i = startCount , j = 0; i < letterIds.length
					&& j < Consts.PAGE_SIZE_RELATION_LETTER; i++, j++) {
				modifiedLetterIds.add(letterIds[i]);
			}
			pageResult.setRecords(letterDao.findLettersByIds(modifiedLetterIds));
			pageResult.setTotal(letterIds.length);
			detail.put("pageResult", pageResult);
			result.setDetail(detail);
		}
		result.setErrorCode(ErrorCode.SUCCESS);
		return result;
	}

	private Integer[] generateLetterIds(List<Link> links) {
		Set<Integer> set = new HashSet<Integer>();
		for (Link link : links) {
			Integer[] letterIds = link.getLetterIds();
			for (int i = 0; i < letterIds.length; i++) {
				if (!set.contains(letterIds[i])) {
					set.add(letterIds[i]);
				}
			}
		}
		Integer[] result = new Integer[set.size()];
		int count = 0;
		for (Integer s : set) {
			result[count++] = s;
		}
		return result;
	}
	
	private Integer[] castToIntegers(String source){
		Integer[] result = null;
		if (source != null) {
			String[] temp = source.split(",");
			result = new Integer[temp.length];
			for (int i = 0; i < temp.length; i++) {
				result[i] = TypeUtils.castToInt(temp[i].trim());
			}
		}
		return result;
	}
}
